﻿using System;
using System.Runtime.CompilerServices;
using System.Diagnostics;
using System.IO;
using System.Reflection;
using log4net;

namespace BellAssistant.Common.CommonHelper
{
    public class LogHelper
    {
        /// <summary>
        /// 获取调用的方法名
        /// </summary>
        /// <returns></returns>
        [MethodImpl(MethodImplOptions.NoInlining)]
        public static string MethodName()
        {
            return new StackFrame(1, false).GetMethod().Name + ": ";
        }

        /// <summary>
        /// 调用的方法名称
        /// </summary>
        /// <returns></returns>
        public static string GetMethodName()
        {
            StackTrace trace = new StackTrace();
            StackFrame frame = trace.GetFrame(1);
            MethodBase method = frame.GetMethod();
            String className = method.ReflectedType.Name;
            return string.Format("类名：[{0}] 方法名：[{1}]", className, method.Name);
        }

        /// <summary>
        /// 调用的当前方法的方法名称(父方法)
        /// </summary>
        /// <returns></returns>
        public static string GetFatherMethodName()
        {
            StackTrace trace = new StackTrace();
            StackFrame frame = trace.GetFrame(2);
            MethodBase method = frame.GetMethod();
            String className = method.ReflectedType.Name;
            //return string.Format("调用页面/类：[{0}] 方法名：[{1}]", className, method.Name);
            return string.Format(" [{0}].[{1}] ", className, method.Name);
        }

        /// <summary>
        /// 显示异常信息并写日志
        /// </summary>
        /// <param name="log">log4net接口类</param>
        /// <param name="errMsg">错误信息</param>
        public static void ShowErrorMsg(ILog logger, string errMsg)
        {
            logger.Error(errMsg); //写日志到本地***Err.log文件
        }

        /// <summary>
        /// 自定义生成日志方法WriteLogDefined()  原WriteLog()
        /// </summary>
        /// <param name="msg"></param>
        public static void WriteLogDefined(string msg)   //原自定义生成日志方法WriteLog()
        {
            string filePath = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "Logs\\");
            string fileName = string.Format("{0}{1}.log", filePath, DateTime.Now.ToString("yyyyMMdd"));
            if (!Directory.Exists(filePath))
            {
                Directory.CreateDirectory(filePath);
            }
            FileInfo fileInfo = new FileInfo(fileName);
            if (!fileInfo.Exists)
            {
                FileStream fs;
                fs = File.Create(fileName);
                fs.Close();
                fileInfo = new FileInfo(fileName);
            }

            using (FileStream fs = fileInfo.OpenWrite())
            {
                StreamWriter sw = new StreamWriter(fs);
                sw.BaseStream.Seek(0, SeekOrigin.End);
                sw.WriteLine(DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss fff：") + msg);

                sw.Flush();
                sw.Close();
            }
        }

        #region log4net

        private static readonly ILog loggerinfo = LogManager.GetLogger("loggerinfo");
        private static readonly ILog loggererror = LogManager.GetLogger("loggererror");
        private static readonly ILog logger = LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType);
        private static LogHelper _instance = new LogHelper();

        //public static LogHelper Instance
        //{
        //    get
        //    {
        //        if (null == _instance)
        //        {
        //            _instance = new LogHelper();
        //        }
        //        return _instance;
        //    }
        //}

        public static LogHelper WriteLog
        {
            get
            {
                //DeleteLog(Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "Logs\\"));
                if (null == _instance)
                {
                    _instance = new LogHelper();
                }
                return _instance;
            }
        }

        /// <summary>
        /// Error
        /// </summary>
        /// <param name="errorMsg"></param>
        /// <param name="ex"></param>
        public void Error(string errorMsg, Exception ex = null)
        {
            if (ex != null)
            {
                //logger.Error(GetFatherMethodName()+errorMsg, ex);
                logger.Error(string.Format("{0}{1}", GetFatherMethodName(), errorMsg), ex);
            }
            else
            {
                logger.Error(string.Format("{0}{1}", GetFatherMethodName(), errorMsg));
            }
        }

        /// <summary>
        /// Info
        /// </summary>
        /// <param name="msg"></param>
        public void Info(string infoMsg)
        {            
            logger.Info(string.Format("{0}{1}", GetFatherMethodName(), infoMsg));
        }       

        /// <summary>
        /// Warn警告
        /// </summary>
        /// <param name="msg"></param>
        public void Warn(string warnMsg)
        {
            logger.Warn(string.Format("{0}{1}", GetFatherMethodName(), warnMsg));
        }

        /// <summary>
        /// Fatal致命错误
        /// </summary>
        /// <param name="msg"></param>

        public void Fatal(string fatalMsg)
        {
            logger.Fatal(string.Format("{0}{1}", GetFatherMethodName(), fatalMsg));
        }

        /// <summary>
        /// Debug
        /// </summary>
        /// <param name="msg"></param>
        public void Debug(string debugMsg)
        {
            logger.Debug(string.Format("{0}{1}", GetFatherMethodName(), debugMsg));
        }

        /// <summary>
        /// Monitor
        /// </summary>
        /// <param name="msg"></param>
        public void Monitor(string msg)
        {
            LogManager.GetLogger("loggermonitor").Info(string.Format("{0}{1}", GetFatherMethodName(), msg));
        }

        /// <summary>
        /// 日志级别isInfoEnabled
        /// </summary>
        bool IsInfoEnabled = logger.IsInfoEnabled;  

        /// <summary>
        /// 日志级别isErrorEnabled
        /// </summary>
        bool IsErrorEnabled = logger.IsErrorEnabled;
        #endregion

        /// <summary>
        /// 删除过期日志
        /// </summary>
        /// <param name="path">日志路径</param>
        /// <param name="days">天数，用于标记删除几天前的日志</param>
        public static void DeleteLog(string path, int days)
        {
            if (string.IsNullOrWhiteSpace(path) || days <= 0)
            {
                return;
            }
            if (Directory.Exists(path))
            {
                LogHelper.WriteLog.Info("========执行定期删除日志========");
                DirectoryInfo dirInfo = new DirectoryInfo(path);
                FileInfo[] files = dirInfo.GetFiles();
                foreach (FileInfo file in files)
                {
                    try
                    {
                        //删除创建日志日期是days天前的日志
                        if (DateTime.Compare(file.CreationTime.AddDays(days), DateTime.Now) < 0)
                        {
                            if (file.Name.Contains(".log") || file.Name.Contains(".Log"))
                            {
                                file.Delete();
                            }                           
                        }
                        //删除最后修改日志日期是days天前的日志
                        if (DateTime.Compare(file.LastWriteTime.AddDays(days), DateTime.Now) < 0)
                        {
                            if (file.Name.Contains(".log") || file.Name.Contains(".Log"))
                                file.Delete();
                        }
                        //删除日志名称日期是days天前的日志
                        if (DateTime.Compare(Convert.ToDateTime(file.Name.Substring(0, 10)), DateTime.Now.AddDays(-days)) < 0)
                        {
                            if (file.Name.Contains(".log") || file.Name.Contains(".Log"))
                                file.Delete();
                        }                       
                    }
                    catch (Exception ex)
                    {
                        LogHelper.WriteLog.Error("删除日志异常：" + ex.Message, ex);
                        continue;
                    }
                }
                LogHelper.WriteLog.Info("=======删除日志成功=======");
            }
        }
       
    }
}
